package org.kornero.example;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Point;
import android.graphics.drawable.ShapeDrawable;
import android.graphics.drawable.shapes.OvalShape;
import android.view.Display;
import android.view.View;
import android.view.WindowManager;
import com.kornero.util.sensor.accelerometr.Rotation;

import java.util.Observable;
import java.util.Observer;

public class BubbleView extends View implements Observer {
    private static final String TAG = BubbleView.class.getSimpleName();
    private static final int MULTIPLEXER = 2;
    private static final int FPS = 60;
    private static final int SPF = 1000 / FPS;

    private final ShapeDrawable bubble;
    private final int diameter;
    private final int maxX;
    private final int maxY;

    private int x;
    private int y;
    private float dx;
    private float dy;

    public BubbleView(Context context) {
        super(context);
        final Point size = getDisplaySize();
        diameter = (size.x + size.y) / (2 * 10);
        maxX = size.x - diameter;
        maxY = size.y - diameter;
        bubble = new ShapeDrawable(new OvalShape());

        this.createBubble();
        this.startUpdateTask();
        Rotation.getInstance().addObserver(this);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        bubble.draw(canvas);
    }

    @Override
    public void update(final Observable observable, final Object data) {
        this.update((float[]) data);
    }

    private void update(final float[] data) {
        this.dx += data[Rotation.X];
        this.dy += data[Rotation.Y];
    }

    private void createBubble() {
        x = maxX / 2;
        y = maxY / 2;

        bubble.setBounds(x, y, x + diameter, y + diameter);
        bubble.getPaint().setColor(0xff74AC23);
    }

    private void update() {
        this.move(dx, dy);
        this.invalidate();
    }

    private void move(float deltaX, float deltaY) {
        x += deltaX * MULTIPLEXER;
        y -= deltaY * MULTIPLEXER;
        if (x < 0) {
            x = 0;
        }
        if (y < 0) {
            y = 0;
        }
        if (x > maxX) {
            x = maxX;
        }
        if (y > maxY) {
            y = maxY;
        }
        bubble.setBounds(x, y, x + diameter, y + diameter);
    }

    private Point getDisplaySize() {
        final WindowManager wm = (WindowManager) this.getContext().getSystemService(Context.WINDOW_SERVICE);
        final Display display = wm.getDefaultDisplay();
        final Point size = new Point();
        display.getSize(size);
        return size;
    }

    private void startUpdateTask() {
        this.postDelayed(new Runnable() {
            @Override
            public void run() {
                update();

                // ReRun task.
                postDelayed(this, SPF);
            }
        }, SPF);
    }
}